package com.jilefojing.dao.impl;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

import tk.mybatis.mapper.entity.Example;
import tk.mybatis.mapper.entity.Example.Criteria;

import com.jilefojing.beans.enums.ItemTypeEnumForSource;
import com.jilefojing.beans.enums.ProgressStatusForSource;
import com.jilefojing.beans.enums.StatusEnumForPublish;
import com.jilefojing.beans.pojos.RCategorySource;
import com.jilefojing.beans.query.RCategorySourceQuery;
import com.jilefojing.beans.query.RCategorySourceQuery.IntersectionCategory;
import com.jilefojing.beans.vo.Pagination;
import com.jilefojing.dao.IRCategorySourceDao;
import com.jilefojing.dao.base.impl.BaseDao;
import com.jilefojing.dao.mapper.IRCategorySourceMapper;
import com.jilefojing.util.Detect;

/**
 * 
 * @author 作者 jgshun
 * @date 创建时间 2016年07月26日 16时40分30秒
 */
@Repository
public class RCategorySourceDao extends BaseDao<RCategorySource> implements
		IRCategorySourceDao {
	@Autowired
	private IRCategorySourceMapper rCategorySourceMapper;

	@Override
	public Pagination<RCategorySource> getPagination(
			RCategorySourceQuery rCategorySourceQuery,
			Pagination<RCategorySource> pagination) {
		Example example = new Example(RCategorySource.class);
		Criteria criteria = example.createCriteria();
		if (Detect.notEmpty(rCategorySourceQuery.getIds())) {
			criteria.andIn(RCategorySource.FIELD_ID,
					rCategorySourceQuery.getIds());
		}

		if (Detect.notEmpty(rCategorySourceQuery.getItemTypes())) {
			List<Short> itemTypeCodes = new ArrayList<Short>();
			for (ItemTypeEnumForSource _ItemType : rCategorySourceQuery
					.getItemTypes()) {
				itemTypeCodes.add(_ItemType.getCode());
			}
			criteria.andIn(RCategorySource.FIELD_ITEMTYPE, itemTypeCodes);
		}

		if (Detect.notEmpty(rCategorySourceQuery.getStatuses())) {
			List<Short> statusCodes = new ArrayList<Short>();
			for (StatusEnumForPublish _status : rCategorySourceQuery
					.getStatuses()) {
				statusCodes.add(_status.getCode());
			}
			criteria.andIn(RCategorySource.FIELD_STATUS, statusCodes);
		}

		if (Detect.notEmpty(rCategorySourceQuery.getItemIds())) {
			criteria.andIn(RCategorySource.FIELD_ITEMID,
					rCategorySourceQuery.getItemIds());
		}

		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC1s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC1,
					rCategorySourceQuery.getCategoryC1s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC2s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC2,
					rCategorySourceQuery.getCategoryC2s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC3s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC3,
					rCategorySourceQuery.getCategoryC3s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC4s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC4,
					rCategorySourceQuery.getCategoryC4s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC5s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC5,
					rCategorySourceQuery.getCategoryC5s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC6s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC6,
					rCategorySourceQuery.getCategoryC6s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC7s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC7,
					rCategorySourceQuery.getCategoryC7s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC8s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC8,
					rCategorySourceQuery.getCategoryC8s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC9s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC9,
					rCategorySourceQuery.getCategoryC9s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC10s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC10,
					rCategorySourceQuery.getCategoryC10s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC11s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC11,
					rCategorySourceQuery.getCategoryC11s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC12s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC12,
					rCategorySourceQuery.getCategoryC12s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC13s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC13,
					rCategorySourceQuery.getCategoryC13s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC14s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC14,
					rCategorySourceQuery.getCategoryC14s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC15s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC15,
					rCategorySourceQuery.getCategoryC15s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC16s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC16,
					rCategorySourceQuery.getCategoryC16s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC17s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC17,
					rCategorySourceQuery.getCategoryC17s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC18s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC18,
					rCategorySourceQuery.getCategoryC18s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC19s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC19,
					rCategorySourceQuery.getCategoryC19s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC20s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC20,
					rCategorySourceQuery.getCategoryC20s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC21s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC21,
					rCategorySourceQuery.getCategoryC21s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC22s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC22,
					rCategorySourceQuery.getCategoryC22s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC23s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC23,
					rCategorySourceQuery.getCategoryC23s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC24s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC24,
					rCategorySourceQuery.getCategoryC24s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC25s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC25,
					rCategorySourceQuery.getCategoryC25s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC26s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC26,
					rCategorySourceQuery.getCategoryC26s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC27s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC27,
					rCategorySourceQuery.getCategoryC27s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC28s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC28,
					rCategorySourceQuery.getCategoryC28s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC29s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC29,
					rCategorySourceQuery.getCategoryC29s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC30s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC30,
					rCategorySourceQuery.getCategoryC30s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC31s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC31,
					rCategorySourceQuery.getCategoryC31s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC32s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC32,
					rCategorySourceQuery.getCategoryC32s());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getCategoryC33s())) {
			criteria.andIn(RCategorySource.FIELD_CATEGORYC33,
					rCategorySourceQuery.getCategoryC33s());
		}
		// TODO 可以继续增加 资源类别

		if (Detect.notEmpty(rCategorySourceQuery.getCreateUserIds())) {
			criteria.andIn(RCategorySource.FIELD_CREATEUSER,
					rCategorySourceQuery.getCreateUserIds());
		}

		if (rCategorySourceQuery.getEqualCreateTime() != null) {
			criteria.andEqualTo(RCategorySource.FIELD_CREATETIME,
					rCategorySourceQuery.getEqualCreateTime());
		}

		if (rCategorySourceQuery.getEqualAndBeforCreateTime() != null) {
			criteria.andGreaterThanOrEqualTo(RCategorySource.FIELD_CREATETIME,
					rCategorySourceQuery.getEqualAndBeforCreateTime());
		}

		if (rCategorySourceQuery.getEqualAndAfterCreateTime() != null) {
			criteria.andLessThanOrEqualTo(RCategorySource.FIELD_CREATETIME,
					rCategorySourceQuery.getEqualAndAfterCreateTime());
		}

		if (rCategorySourceQuery.getBeforCreateTime() != null) {
			criteria.andGreaterThan(RCategorySource.FIELD_CREATETIME,
					rCategorySourceQuery.getBeforCreateTime());
		}

		if (rCategorySourceQuery.getAfterCreateTime() != null) {
			criteria.andLessThan(RCategorySource.FIELD_CREATETIME,
					rCategorySourceQuery.getAfterCreateTime());
		}
		if (Detect.notEmpty(rCategorySourceQuery.getIntersectionCategories())) {
			String intersectionCategoriesCondition = this
					.getIntersectionCategoriesCondition(rCategorySourceQuery
							.getIntersectionCategories());
			if (Detect.notEmpty(intersectionCategoriesCondition)) {
				criteria.andCondition(intersectionCategoriesCondition);
			}
		}

		if (Detect.notEmpty(pagination.getOrders())) {
			example.setOrderByClause(pagination.getOrdersToStr());
		}

		return super.getPagination(pagination, example);
	}

	private String getIntersectionCategoriesCondition(
			List<IntersectionCategory> intersectionCategories) {
		List<StringBuilder> valBuds = new ArrayList<StringBuilder>();

		for (IntersectionCategory _IntersectionCategory : intersectionCategories) {
			if (Detect.notEmpty(_IntersectionCategory.getChilds())) {
				StringBuilder valPartBud = new StringBuilder();

				for (int i = 0; i < _IntersectionCategory.getChilds().size(); i++) {
					long childCategory = _IntersectionCategory.getChilds().get(
							i);
					if (childCategory > 0) {
						if (i == 0) {
							valPartBud.append(
									RCategorySource.COLUMN_CATEGORY_ID).append(
									" in ( ");
						}

						valPartBud.append(childCategory);

						if (i == _IntersectionCategory.getChilds().size() - 1) {
							valPartBud.append(" ) ");
						} else {
							valPartBud.append(" , ");
						}
					}
				}

				if (valPartBud.length() > 0) {
					valBuds.add(valPartBud);
				}
			}
		}

		if (Detect.notEmpty(valBuds)) {
			StringBuilder valBudAll = new StringBuilder();
			valBudAll.append(" ( ");
			for (int i = 0; i < valBuds.size(); i++) {
				StringBuilder _bud = valBuds.get(i);
				valBudAll.append(_bud);
				if (i < valBuds.size() - 1) {
					valBudAll.append(" and ");
				}
			}
			valBudAll.append(" ) ");
			// ( category_id in (1,2,3) and category_id in (456) )
			return valBudAll.toString();
		}

		return null;
	}

	public static void main(String[] args) {
		List<Long> ids = new ArrayList<Long>();
		for (int i = 0; i < 10; i += 2) {
			System.out.println(i);
		}
	}

	@Override
	public Pagination<RCategorySource> getPaginationByCategoryIdsForIntersection(
			List<String> intersectionCategoryConditions,
			List<StatusEnumForPublish> statuses,
			List<ItemTypeEnumForSource> returnItemTypes,
			List<ProgressStatusForSource> progressStatuses,
			Pagination<RCategorySource> pagination) {

		if (pagination.isCounted()) {
			int count = rCategorySourceMapper
					.countForIntersectionCategoryConditions(
							intersectionCategoryConditions, statuses,
							returnItemTypes, progressStatuses);
			pagination.setCount(count);
			if (count < 1) {
				return pagination;
			}
		}

		List<RCategorySource> rCategorySources = rCategorySourceMapper
				.getListForIntersectionCategoryConditions(
						intersectionCategoryConditions, statuses,
						returnItemTypes, progressStatuses, pagination);

		pagination.setItems(rCategorySources);
		return pagination;
	}

	@Override
	public List<RCategorySource> getListByItem(ItemTypeEnumForSource itemType,
			long itemId) {
		return this.getListByItems(itemType,
				Arrays.asList(new Long[] { itemId }));
	}

	@Override
	public List<RCategorySource> getListByItems(ItemTypeEnumForSource itemType,
			List<Long> itemIds) {
		Example example = new Example(RCategorySource.class);
		example.createCriteria()
				.andEqualTo(RCategorySource.FIELD_ITEMTYPE, itemType.getCode())
				.andIn(RCategorySource.FIELD_ITEMID, itemIds);
		return super.getListByExample(example);
	}

	@Override
	public void updateByIds(List<RCategorySource> categorySources) {
		rCategorySourceMapper.updateByIds(categorySources);
	}

	@Override
	public int countByCategory(String categoryKey, long categoryId) {
		return this.countByCategories(categoryKey,
				Arrays.asList(new Long[] { categoryId }));
	}

	@Override
	public int countByCategories(String categoryKey, List<Long> categoryIds) {
		Example example = new Example(RCategorySource.class);
		categoryKey = categoryKey.substring(0, 1).toUpperCase()
				+ categoryKey.substring(1);
		example.createCriteria().andIn("category" + categoryKey, categoryIds);
		return super.countByExample(example);
	}

	@Override
	public List<RCategorySource> getListByCategories(String categoryKey,
			List<Long> categoryIds) {
		Example example = new Example(RCategorySource.class);
		categoryKey = categoryKey.substring(0, 1).toUpperCase()
				+ categoryKey.substring(1);
		example.createCriteria().andIn("category" + categoryKey, categoryIds);
		return super.getListByExample(example);
	}
}
